/*
 * Copyright (c) 2006-2021, RT-Thread Development Team
 *
 * SPDX-License-Identifier: Apache-2.0
 *
 * Change Logs:
 * Date           Author       Notes
 * 2024-09-27     huger       the first version
 */

#include "app_io.h"

#ifdef __cplusplus
extern "C" {
#endif /* __cplusplus */

#define bool
#include <qled.h>
#undef bool

#ifdef __cplusplus
}
#endif /* __cplusplus */


#define DBG_TAG "io"
#define DBG_LVL DBG_LOG
#include <rtdbg.h>

const uint32_t key_pin[8] = {
        GET_PIN(B, 12),
        GET_PIN(B, 13),
        GET_PIN(B, 14),
        GET_PIN(B, 15),
        GET_PIN(C, 6),
        GET_PIN(C, 7),
        GET_PIN(C, 8),
        GET_PIN(C, 9),
};
const uint32_t sensor_pin[3]={
        GET_PIN(B,6),
        GET_PIN(B,7),
        GET_PIN(B,8),
};

const uint32_t led_pin = GET_PIN(B,3);

static bitfilter_t key_filter[8];
static bitfilter_t sensor_filter[3];

iomap gpio_map;

static void input_fulsh(iomap* map)
{
    int bitval = 0;

    for(uint32_t i = 0 ; i < sizeof(key_pin) / sizeof(uint32_t); i++)
    {
        bitval = rt_pin_read(key_pin[i]);
        mod_bitfilter_poll(!bitval, key_filter + i);
        map->key_st[i] = !mod_bitfilter_state(key_filter + i);
    }

    for(uint32_t i = 0 ; i < sizeof(sensor_pin) / sizeof(uint32_t); i++)
    {
        bitval = rt_pin_read(sensor_pin[i]);
        mod_bitfilter_poll(bitval, sensor_filter + i);
        map->sensor_st[i] = !mod_bitfilter_state(sensor_filter + i);
    }

}


static void app_io_thread_entry(void* param)
{
    while(1)
    {

        iomap map = {0};

        rt_enter_critical();
        memcpy(&map, param, sizeof(iomap));
        rt_exit_critical();

        input_fulsh(&map);

        rt_enter_critical();
        memcpy(param, &map, sizeof(iomap));
        rt_exit_critical();

        rt_thread_mdelay(10);
    }
}

void app_io_init(void)
{
    uint32_t i;
    iomap* map = &gpio_map;

    //初始化滤波结构体
    for(i = 0 ; i < sizeof(key_filter) / sizeof(bitfilter_t); i++)
        mod_bitfilter_init(key_filter + i, 5, 5);

    for(i = 0 ; i < sizeof(sensor_filter) / sizeof(bitfilter_t); i++)
        mod_bitfilter_init(sensor_filter + i, 5, 5);

    //输入引脚初始化
    for(i = 0 ; i < sizeof(key_pin) / sizeof(uint32_t); i++)
        rt_pin_mode(key_pin[i], PIN_MODE_INPUT);

    for(i = 0 ; i < sizeof(sensor_pin) / sizeof(uint32_t); i++)
        rt_pin_mode(sensor_pin[i], PIN_MODE_INPUT);


    for(int i = 0; i < 10; i++)
    {
        input_fulsh(map);
        rt_thread_mdelay(5);
    }

    //输出引脚初始化
    rt_pin_mode(led_pin, PIN_MODE_OUTPUT);
    qled_add(led_pin, 1);
//    qled_set_off(led_pin);

    qled_set_blink(led_pin,1000,1000);

    rt_thread_t thread = rt_thread_create("io", app_io_thread_entry, map,
                                  1024, 14, 20);

    if (thread == RT_NULL)
    {
        LOG_D("io_thread error");
    }
    else{
        LOG_D("io_thread success.");
    }
    rt_thread_startup(thread);

}

void app_io_get_gpio_map(iomap* map)
{
    rt_enter_critical();
    memcpy(map, &gpio_map, sizeof(iomap));
    rt_exit_critical();
}

void app_io_set_gpio_map(iomap* map)
{
    rt_enter_critical();
    memcpy(&gpio_map, map, sizeof(iomap));
    rt_exit_critical();
}


static int dbg_io_info(int argc, char *argv[])
{
    uint32_t i;

    for(i = 0 ; i < sizeof(gpio_map.key_st) / sizeof(uint8_t); i++)
        LOG_I("key_st[%d] = %d", i, gpio_map.key_st[i]);

    for(i = 0 ; i < sizeof(gpio_map.sensor_st) / sizeof(uint8_t); i++)
        LOG_I("sense_st[%d] = %d", i, gpio_map.sensor_st[i]);

    return RT_EOK;
}
MSH_CMD_EXPORT(dbg_io_info, 获取io信息);
